package com.fub.view;

import java.util.List;
import java.util.Map;

import android.app.Activity;
import android.app.Dialog;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.os.Bundle;
import android.util.DisplayMetrics;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.inputmethod.InputMethodManager;
import android.widget.ArrayAdapter;
import android.widget.AutoCompleteTextView;
import android.widget.Button;
import android.widget.EditText;
import android.widget.FrameLayout;
import android.widget.LinearLayout;
import android.widget.Toast;
import android.widget.ZoomControls;

import com.fub.R;
import com.fub.guidance.Building;
import com.fub.guidance.BuildingDAO;
import com.fub.guidance.Edge;
import com.fub.guidance.Graph;
import com.fub.guidance.Point;
import com.fub.guidance.Relation;
import com.fub.guidance.RoomDataDAO;
import com.fub.guidance.RoutingGraphDAO;
import com.fub.guidance.Vertex;
import com.fub.guidance.Vertex.Type;
import com.fub.guidance.Wall;
import com.fub.positioning.FingerprintService;
import com.fub.positioning.ReferencePoint;
import com.fub.positioning.ReferencePointDAO;
import com.fub.positioning.WifiRecorder;
import com.fub.update.BuildingUpdate;
import com.fub.util.PreferenceDAO;
import com.fub.util.Util;

public class MapActivity extends Activity {

	private static final int DIALOG_SOURCE = 0;
	private static final int DIALOG_DESTINATION = 1;
	private static final int OPTION_SEARCH = 0;
	private static final int OPTION_ROUTE = 1;
	private static final int OPTION_MY_POSITION = 2;
	private static final int OPTION_SHOW_SETTINGS = 3;
	private static final int OPTION_FINGERPRINT_MODE = 4;
	private static final int OPTION_HIDE_UI = 5;
	private static final int OPTION_FOLLOW_ROUTE = 6;
	private static final float ZOOM_STEP = 2.0f;
	private PreferenceDAO preferenceDao;
	private RoutingGraphDAO nodeEdgeDBService;
	private BuildingDAO wallDbService;
	private RoomDataDAO updateDBService;
	private Graph graph;
	private Dialog choiseDestinationDialog;
	private Dialog choiseSourceDialog;
	private Dialog searchDialog;
	private Vertex routingSource;
	private boolean startIsSet = false;
	private boolean endIsSet = false;
	private FingerprintService fingerprintManager;
	private WifiRecorder recorder;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		this.preferenceDao = new PreferenceDAO(this);
		this.nodeEdgeDBService = new RoutingGraphDAO(this);
		this.wallDbService = new BuildingDAO(this);
		this.updateDBService = new RoomDataDAO(this);
		this.fingerprintManager = FingerprintService.getInstance(this);
		this.fingerprintManager.reset();
		this.recorder = WifiRecorder.getInstance(this);
		initGraphWithUpdatesAndRelations();
		initBuilding();
		setContentView(R.layout.map);
		addZoomElement();
		setDisplayDimensionsToPreferences();
		initRoutingComponents();
		initSearchComponents();
		initPositioningComponents();
		initDetailBtn();
		List<Vertex> matchingNodes = Util.getMatchingNodes("Eingang",
				this.graph.getNodes());
		setPositonWithChoiseDialog("Eingang", matchingNodes);
	}


	private void initGraphWithUpdatesAndRelations() {
		this.graph = Graph.getInstance();
		List<Vertex> nodes = this.nodeEdgeDBService.getNodes(this.preferenceDao
				.getBuildingId());
		for (Vertex node : nodes) {
			if (node.getType() == Type.ROOM) {
				Map<String, String> properties = this.updateDBService
						.getRoomData(this.preferenceDao.getBuildingId(),
								node.getLabel());
				node.setProperties(properties);
			}
		}
		this.graph.addNodes(nodes);

		List<Edge> edges = this.nodeEdgeDBService.getEdges(this.preferenceDao
				.getBuildingId());
		for (Edge edge : edges) {
			String sourceId = edge.getSourceId();
			String destinationId = edge.getDestinationId();
			Vertex source = this.graph.getNodeById(sourceId);
			Vertex destination = this.graph.getNodeById(destinationId);
			source.addEdge(edge);
			destination.addEdge(edge);
		}
		this.graph.setEdges(edges);
		this.graph.calculateEdgeWeights(this.preferenceDao);
		List<Relation> relations = this.nodeEdgeDBService
				.getAllRelations(this.preferenceDao.getBuildingId());
		this.graph.addRealtions(relations);
	}

	private void initBuilding() {
		Building building = Building.getInstance();
		String buildingId = this.preferenceDao.getBuildingId();
		List<Wall> walls = this.wallDbService.getWalls(buildingId);
		building.setWalls(walls);
	}

	private void setDisplayDimensionsToPreferences() {
		DisplayMetrics displaymetrics = new DisplayMetrics();
		getWindowManager().getDefaultDisplay().getMetrics(displaymetrics);
		this.preferenceDao.setScreenWidth(displaymetrics.widthPixels);
		this.preferenceDao.setScreenHeight(displaymetrics.heightPixels);
	}

	private void setPositonWithChoiseDialog(String input,
			final List<Vertex> matchingNodes) {
		String title = String.format(
				getResources().getString(R.string.whichRoom), input);
		final CharSequence[] items = Util.getFormatedNodeStrings(matchingNodes);
		if (input.equals("Eingang")) {
			title = getResources().getString(R.string.whereToStart);
		}
		this.searchDialog = Util.showChoiseDialog(this.searchDialog, title,
				items, new DialogInterface.OnClickListener() {
					@Override
					public void onClick(DialogInterface dialog, int item) {
						Vertex choise = matchingNodes.get(item);
						setMapPositionAndRefresh(choise.getPosition());
						MapActivity.this.preferenceDao.setSelectedNodeId(choise
								.getId());
						MapActivity.this.searchDialog.hide();
					}
				}, this);
	}

	private void initDetailBtn() {
		findViewById(R.id.btnDetails).setOnClickListener(
				new BtnShowRoomDataListener());
	}

	private void setMapPositionAndRefresh(Point to) {
		this.preferenceDao.setPosition(Util.calculateZoomedPosition(to,
				this.preferenceDao));
		this.preferenceDao.setEtage(to.getZ());
		refreshLayout();
	}

	private void addZoomElement() {
		ZoomControls zoomControls = (ZoomControls) findViewById(R.id.ZoomControls01);
		zoomControls.setOnZoomInClickListener(new OnClickListener() {
			@Override
			public void onClick(View v) {
				if (MapActivity.this.preferenceDao.getZoomFactor() < 1.0f) {
					float newX = MapActivity.this.preferenceDao.getPosition()
							.getX() * ZOOM_STEP;
					float newY = MapActivity.this.preferenceDao.getPosition()
							.getY() * ZOOM_STEP;
					MapActivity.this.preferenceDao
							.setZoomFactor((MapActivity.this.preferenceDao
									.getZoomFactor() * ZOOM_STEP));
					MapActivity.this.preferenceDao
							.setPosition(new Point((int) newX, (int) newY,
									MapActivity.this.preferenceDao
											.getPosition().getZ()));
					refreshLayout();
				}
			}
		});
		zoomControls.setOnZoomOutClickListener(new OnClickListener() {
			@Override
			public void onClick(View v) {
				float newX = MapActivity.this.preferenceDao.getPosition()
						.getX() / ZOOM_STEP;
				float newY = MapActivity.this.preferenceDao.getPosition()
						.getY() / ZOOM_STEP;
				MapActivity.this.preferenceDao
						.setZoomFactor(((MapActivity.this.preferenceDao
								.getZoomFactor()) / ZOOM_STEP));
				MapActivity.this.preferenceDao.setPosition(new Point(
						(int) newX, (int) newY, MapActivity.this.preferenceDao
								.getPosition().getZ()));
				refreshLayout();
			}
		});
	}

	// Routing components
	private void initRoutingComponents() {
		addContentToAutocomplete(this.graph.getAllRoomLabels(), R.id.editSource);
		addContentToAutocomplete(this.graph.getAllRoomLabels(),
				R.id.editDestination);
		findViewById(R.id.btnCalculateRoute).setOnClickListener(
				new BtnRouteListener());
	}

	private void showRoutePanel() {
		resetOldRoute();
		LinearLayout routePanel = (LinearLayout) (findViewById(R.id.routePanel));
		routePanel.setVisibility(View.VISIBLE);
	}

	private void hideRoutePanel() {
		LinearLayout routePanel = (LinearLayout) (findViewById(R.id.routePanel));
		routePanel.setVisibility(View.GONE);
		routePanel.setVisibility(View.GONE);
		EditText editText = (EditText) (findViewById(R.id.editPosition));
		((InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE))
				.hideSoftInputFromWindow(editText.getWindowToken(), 0);
	}

	private void resetOldRoute() {
		this.startIsSet = false;
		this.endIsSet = false;
		this.preferenceDao.setRoutingStart(PreferenceDAO.NO_NODE_SET);
		this.preferenceDao.setRoutingEnd(PreferenceDAO.NO_NODE_SET);
		this.preferenceDao.setRoutingDisabled();
	}

	private void setRoutingNodesWithChoiseDialogg(final int type, String input,
			final List<Vertex> matchingSourceNodes) {
		final CharSequence[] items = Util
				.getFormatedNodeStrings(matchingSourceNodes);
		String title = String.format(
				getResources().getString(R.string.whichRoom), input);
		DialogInterface.OnClickListener listener = new DialogInterface.OnClickListener() {
			@Override
			public void onClick(DialogInterface dialog, int item) {
				Vertex choise = matchingSourceNodes.get(item);
				if (type == DIALOG_SOURCE) {
					MapActivity.this.preferenceDao.setRoutingStart(choise
							.getId());
					MapActivity.this.routingSource = choise;
					MapActivity.this.startIsSet = true;
				} else if (type == DIALOG_DESTINATION) {
					MapActivity.this.preferenceDao.setSelectedNodeId(choise
							.getId());
					MapActivity.this.preferenceDao
							.setRoutingEnd(choise.getId());
					MapActivity.this.endIsSet = true;
				}
				if (type == DIALOG_SOURCE) {
					MapActivity.this.choiseSourceDialog.hide();
				} else if (type == DIALOG_DESTINATION) {
					MapActivity.this.choiseDestinationDialog.hide();
				}
				if (MapActivity.this.startIsSet && MapActivity.this.endIsSet) {
					MapActivity.this.preferenceDao.setRoutingEnabled();
					setMapPositionAndRefresh(MapActivity.this.graph
							.getNodeById(MapActivity.this.routingSource.getId())
							.getPosition());
					hideRoutePanel();
				}
			}
		};
		if (type == DIALOG_SOURCE) {
			this.choiseSourceDialog = Util.showChoiseDialog(
					this.choiseSourceDialog, title, items, listener, this);
		} else if (type == DIALOG_DESTINATION) {
			this.choiseDestinationDialog = this.choiseSourceDialog = Util
					.showChoiseDialog(this.choiseSourceDialog, title, items,
							listener, this);
		}
	}

	// Positioning components

	private void initPositioningComponents() {
		// show fingerprint panel
		if (this.preferenceDao.isFingerprintEnabled()) {
			findViewById(R.id.FingerprintPanel).setVisibility(View.VISIBLE);
		}
		// add reference point
		Button btnAddReferencePoint = (Button) findViewById(R.id.btnAddReferencePoint);
		btnAddReferencePoint
				.setOnClickListener(new BtnAddReferencePointListener());
		// spread dummy reference points
		Button btnSpreadReferencePoints = (Button) findViewById(R.id.btnSpreadReferencePoints);
		btnSpreadReferencePoints
				.setOnClickListener(new BtnSpredReferencePointListener());
		// delete reference point
		Button btnDeleteReferencePoint = (Button) findViewById(R.id.btnDeleteReferencePoint);
		btnDeleteReferencePoint
				.setOnClickListener(new BtnDeleteReferencePointListener());
		// load reference points
		Button btnLoadReferencePoints = (Button) findViewById(R.id.btnLoadReferencePoints);
		btnLoadReferencePoints
				.setOnClickListener(new BtnLoadReferencePointListener());
		// measure aps
		Button bntMeasureRP = (Button) findViewById(R.id.btnMeasureReferencePoint);
		bntMeasureRP.setOnClickListener(new BtnMeasureRPListener());
		// save reference points
		Button btnSaveReferencePoints = (Button) findViewById(R.id.btnSaveReferencePoints);
		btnSaveReferencePoints
				.setOnClickListener(new BtnSaveReferencePointListener());
		// start and stop record measurement
		Button btnStartStopRecordMeasurements = (Button) findViewById(R.id.btnRecordMeasurements);
		btnStartStopRecordMeasurements
				.setOnClickListener(new BtnRecordsListener());
		// play saved measurings
		Button playRecordReferencePoints = (Button) findViewById(R.id.btnPlayRecordReferencePoints);
		playRecordReferencePoints
				.setOnClickListener(new BtnPlaySavedMeasuringsListener());
		// add measure Distanz
		Button btnMeasureDistance = (Button) findViewById(R.id.btnMeasureDistance);
		btnMeasureDistance.setOnClickListener(new BtnMeasureDistanceListener());
	}

	// Searching components

	private void showSearchPanel() {
		LinearLayout searchPanel = (LinearLayout) (findViewById(R.id.searchPanel));
		searchPanel.setVisibility(View.VISIBLE);
	}

	private void initSearchComponents() {
		addContentToAutocomplete(this.graph.getAllRoomLabels(),
				R.id.editPosition);
		findViewById(R.id.btnSearchNode).setOnClickListener(
				new BtnSearchListener());
	}

	private void hideSearchPanel() {
		LinearLayout routePanel = (LinearLayout) (findViewById(R.id.searchPanel));
		routePanel.setVisibility(View.GONE);
		EditText editText = (EditText) (findViewById(R.id.editPosition));
		((InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE))
				.hideSoftInputFromWindow(editText.getWindowToken(), 0);
	}

	// Option menu
	@Override
	public boolean onCreateOptionsMenu(Menu menu) {
		boolean result = super.onCreateOptionsMenu(menu);
		menu.add(OPTION_SEARCH, OPTION_SEARCH, OPTION_SEARCH,
				getResources().getString(R.string.option_search)).setIcon(
				R.drawable.search);
		menu.add(OPTION_ROUTE, OPTION_ROUTE, OPTION_ROUTE,
				getResources().getString(R.string.option_route)).setIcon(
				R.drawable.route);
		menu.add(OPTION_MY_POSITION, OPTION_MY_POSITION, OPTION_MY_POSITION,
				getResources().getString(R.string.option_my_position)).setIcon(
				R.drawable.location);
		menu.add(OPTION_SHOW_SETTINGS, OPTION_SHOW_SETTINGS,
				OPTION_SHOW_SETTINGS,
				getResources().getString(R.string.option_settings)).setIcon(
				R.drawable.settings);
		menu.add(OPTION_FOLLOW_ROUTE, OPTION_FOLLOW_ROUTE, OPTION_FOLLOW_ROUTE,
				getResources().getString(R.string.option_follow_route));
		menu.add(OPTION_FINGERPRINT_MODE, OPTION_FINGERPRINT_MODE,
				OPTION_FINGERPRINT_MODE,
				getResources().getString(R.string.option_developer_mode));
		return result;
	}

	private boolean followRouteThreadRuns = false;

	private void followRoute() {
		if (this.graph.getShortestPath() == null)
			return;
		Runnable r1 = new Runnable() {
			public void run() {
				try {
					if (MapActivity.this.followRouteThreadRuns)
						return;
					MapActivity.this.followRouteThreadRuns = true;
					Vertex start = null;
					List<Vertex> shortestPath = MapActivity.this.graph
							.getShortestPath();
					int startVertex = 0;
					for (Vertex vertex : shortestPath) {
						if (vertex.getPosition().getZ() == MapActivity.this.preferenceDao
								.getCurrentEtage()) {
							start = vertex;
							break;
						}
						startVertex++;
					}
					if (start == null)
						return;
					Point fromOnDisplay = Util
							.calculateZoomedPosition(start.getPosition(),
									MapActivity.this.preferenceDao);
					MapActivity.this.preferenceDao.setPosition(fromOnDisplay);
					refreshLayout();
					for (int i = startVertex + 1; i < shortestPath.size(); i++) {
						Vertex to = shortestPath.get(i);
						if (fromOnDisplay.getZ() != to.getPosition().getZ()) {
							MapActivity.this.preferenceDao.setEtage(to
									.getPosition().getZ());
						}
						Point toOnDisplay = Util.calculateZoomedPosition(
								to.getPosition(),
								MapActivity.this.preferenceDao);
						double diffX = toOnDisplay.getX()
								- fromOnDisplay.getX();
						double diffY = toOnDisplay.getY()
								- fromOnDisplay.getY();
						double MAX = 2;
						if (diffX > diffY) {
							MAX = Math.abs(diffX) / 1;
						} else {
							MAX = Math.abs(diffY) / 1;
						}
						double xfactor = diffX / MAX;
						double yfactor = diffY / MAX;
						for (int k = 0; k < MAX; k++) {
							int x = fromOnDisplay.getX() + (int) (k * xfactor);
							int y = fromOnDisplay.getY() + (int) (k * yfactor);
							int z = fromOnDisplay.getZ();
							MapActivity.this.preferenceDao
									.setPosition(new Point(x, y, z));
							Thread.sleep(30);
							refreshLayout();
						}
						fromOnDisplay = toOnDisplay;
					}
					MapActivity.this.followRouteThreadRuns = false;
				} catch (InterruptedException iex) {
				}
			}
		};
		new Thread(r1).start();
	}

	@Override
	public boolean onOptionsItemSelected(MenuItem item) {
		switch (item.getItemId()) {
		case OPTION_SHOW_SETTINGS:
			startActivity(new Intent(this, Preferences.class));
			break;
		case OPTION_ROUTE:
			showRoutePanel();
			break;
		case OPTION_MY_POSITION:
			setMapToUserPosition();
			break;
		case OPTION_SEARCH:
			showSearchPanel();
			break;
		case OPTION_FINGERPRINT_MODE:
			if (this.preferenceDao.isFingerprintEnabled()) {
				this.preferenceDao.disableFingerprintMode();
				findViewById(R.id.FingerprintPanel).setVisibility(View.GONE);
			} else {
				this.preferenceDao.enableFingerprintMode();
				findViewById(R.id.FingerprintPanel).setVisibility(View.VISIBLE);
			}
			break;
		case OPTION_HIDE_UI:
			boolean isVisible = (findViewById(R.id.FingerprintPanel)
					.getVisibility() == View.VISIBLE);
			int visibility = View.VISIBLE;
			if (isVisible) {
				visibility = View.GONE;
			}
			findViewById(R.id.ZoomControls01).setVisibility(visibility);
			findViewById(R.id.FingerprintPanel).setVisibility(visibility);
			findViewById(R.id.levelChanger).setVisibility(visibility);
			break;
		case OPTION_FOLLOW_ROUTE:
			followRoute();
			break;
		}
		return super.onOptionsItemSelected(item);
	}

	// other
	private void setMapToUserPosition() {
		FingerprintService fingerprintService = FingerprintService
				.getInstance(this);
		this.recorder.loadSavedReferencePoints();
		Point kwnnPosition = fingerprintService
				.doSingleMeasurementAndReturnKWNNPosition();
		setMapPositionAndRefresh(kwnnPosition);
	}

	private void addContentToAutocomplete(List<String> roomsAndPersonsList,
			int component) {
		String str[] = new String[roomsAndPersonsList.size()];
		String[] roomsAndPersonsStrings = roomsAndPersonsList.toArray(str);
		ArrayAdapter<String> adapter = new ArrayAdapter<String>(this,
				android.R.layout.simple_dropdown_item_1line,
				roomsAndPersonsStrings);
		AutoCompleteTextView textViewSource = (AutoCompleteTextView) findViewById(component);
		textViewSource.setAdapter(adapter);
	}

	private String getInputFromAutocomplete(int viewId) {
		AutoCompleteTextView autoCompleteTextView = (AutoCompleteTextView) findViewById(viewId);
		String inputSource = autoCompleteTextView.getText().toString();
		return inputSource;
	}

	public void refreshLayout() {
		FrameLayout layout = (FrameLayout) findViewById(R.id.maplayout);
		layout.postInvalidate();
	}

	@Override
	public void onBackPressed() {
		LinearLayout routePanel = (LinearLayout) (findViewById(R.id.routePanel));
		LinearLayout searchPanel = (LinearLayout) (findViewById(R.id.searchPanel));
		if (routePanel.getVisibility() == View.VISIBLE) {
			hideRoutePanel();
		} else if (searchPanel.getVisibility() == View.VISIBLE) {
			hideSearchPanel();
		} else {
			ReferencePointDAO dbService = new ReferencePointDAO(this);
			for (ReferencePoint referencePoint : this.fingerprintManager
					.getReferencePoints()) {
				dbService.insertReferencePoint(referencePoint);
			}
			this.fingerprintManager.disableMeasuringThread();
			MapActivity.this.finish();
		}
	}

	// listeners
	class BtnRecordsListener implements OnClickListener {
		@Override
		public void onClick(View v) {
			if (!MapActivity.this.fingerprintManager.isRecording()) {
				MapActivity.this.recorder.startRecordMeasurements();
				((Button) v).setText(getResources().getString(
						R.string.btn_record_stop));
			} else {
				MapActivity.this.recorder.stopAnSaveRecordMeasurements();
				Toast.makeText(
						v.getContext(),
						getResources().getString(R.string.measurementsSaved)
								+ MapActivity.this.fingerprintManager
										.getRecordedMeasurements().size()
								+ "/"
								+ FingerprintService.NUMBER_MEASUREMENTS_FOR_POSITIONING,
						Toast.LENGTH_LONG).show();
				((Button) v).setText(getResources().getString(
						R.string.btnRecordReferencePoints));
			}
		}
	}

	class BtnAddReferencePointListener implements OnClickListener {
		@Override
		public void onClick(View v) {
			MapActivity.this.preferenceDao.enableAddFingerprintMode();
			MapActivity.this.preferenceDao.disableDeleteFingerprintMode();
		}
	}

	class BtnSpredReferencePointListener implements OnClickListener {
		@Override
		public void onClick(View v) {
			MapActivity.this.fingerprintManager
					.createEvenSpreadReferencePoints(180);
		}
	}

	class BtnDeleteReferencePointListener implements OnClickListener {
		@Override
		public void onClick(View v) {
			MapActivity.this.preferenceDao.enableDeleteFingerprintMode();
			MapActivity.this.preferenceDao.disableAddFingerprintMode();
		}
	}

	class BtnLoadReferencePointListener implements OnClickListener {
		@Override
		public void onClick(View v) {
			MapActivity.this.recorder.loadSavedReferencePoints();
			Toast.makeText(
					v.getContext(),
					getResources().getString(R.string.reference_points_loaded)
							+ MapActivity.this.fingerprintManager
									.getReferencePoints().size(),
					Toast.LENGTH_LONG).show();
		}
	}

	class BtnSaveReferencePointListener implements OnClickListener {
		@Override
		public void onClick(View v) {
			MapActivity.this.recorder.saveCurrentReferencePoints();
			Toast.makeText(
					v.getContext(),
					getResources().getString(R.string.reference_points_saved)
							+ MapActivity.this.fingerprintManager
									.getReferencePoints().size(),
					Toast.LENGTH_LONG).show();
		}
	}

	class BtnPlaySavedMeasuringsListener implements OnClickListener {
		@Override
		public void onClick(View v) {
			if (MapActivity.this.recorder.isPlayingSavedMeasurings()) {
				((Button) v).setText(getResources().getString(
						R.string.btnPlayRecordReferencePoints));
				MapActivity.this.recorder.stopPlayingSavedMeasurings();
			} else {
				((Button) v).setText(getResources().getString(
						R.string.btnPlayRecordStop));
				MapActivity.this.recorder.playSavedMeasurings();
			}
		}
	}

	class BtnMeasureRPListener implements OnClickListener {
		@Override
		public void onClick(View v) {
			if (MapActivity.this.fingerprintManager.isMeasureRP()) {
				((Button) v).setText(getResources().getString(
						R.string.btn_measure_referencepoint));
				MapActivity.this.fingerprintManager.setMeasureRP(false);
			} else {
				((Button) v).setText(getResources().getString(
						R.string.btn_measure_stop));
				MapActivity.this.fingerprintManager.setMeasureRP(true);
			}
		}
	}

	class BtnMeasureDistanceListener implements OnClickListener {

		@Override
		public void onClick(View v) {
			MapActivity.this.fingerprintManager.isMeasureDistance = true;
		}

	}

	class BtnSearchListener implements OnClickListener {
		@Override
		public void onClick(View v) {
			String input = ((AutoCompleteTextView) findViewById(R.id.editPosition))
					.getText().toString();
			List<Vertex> matchingNodes = Util.getMatchingNodes(input,
					MapActivity.this.graph.getNodes());
			findViewById(R.id.btnDetails).setVisibility(View.VISIBLE);
			if (matchingNodes.size() > 1) {
				setPositonWithChoiseDialog(input, matchingNodes);
				hideSearchPanel();
			} else if (matchingNodes.size() == 1) {
				setMapPositionAndRefresh(matchingNodes.get(0).getPosition());
				MapActivity.this.preferenceDao.setSelectedNodeId(matchingNodes
						.get(0).getId());
				hideSearchPanel();
			} else if (matchingNodes.size() == 0) {
				Util.showSimpleDialog(
						getResources().getString(R.string.destinationNotFound),
						v.getContext());
			}
		}
	}

	class BtnShowRoomDataListener implements OnClickListener {
		@Override
		public void onClick(View v) {
			startActivity(new Intent(v.getContext(), DetailActivity.class));
		}
	}

	class BtnRouteListener implements OnClickListener {
		@Override
		public void onClick(View v) {
			// handle destination
			String destinationInput = getInputFromAutocomplete(R.id.editDestination);
			List<Vertex> matchingDestinationNodes = Util.getMatchingNodes(
					destinationInput, MapActivity.this.graph.getNodes());
			if (matchingDestinationNodes.size() > 1) {
				setRoutingNodesWithChoiseDialogg(DIALOG_DESTINATION,
						destinationInput, matchingDestinationNodes);
			} else if (matchingDestinationNodes.size() == 1) {
				MapActivity.this.endIsSet = true;
				MapActivity.this.preferenceDao
						.setSelectedNodeId(matchingDestinationNodes.get(0)
								.getId());
				MapActivity.this.preferenceDao
						.setRoutingEnd(matchingDestinationNodes.get(0).getId());
			} else if (matchingDestinationNodes.size() == 0) {
				Util.showSimpleDialog(
						String.format(getResources().getString(
								R.string.destinationNotFound)), v.getContext());
			}

			// handle source
			String sourceInput = getInputFromAutocomplete(R.id.editSource);
			List<Vertex> matchingSourceNodes = Util.getMatchingNodes(
					sourceInput, MapActivity.this.graph.getNodes());
			if (matchingSourceNodes.size() > 1) {
				setRoutingNodesWithChoiseDialogg(DIALOG_SOURCE, sourceInput,
						matchingSourceNodes);
			} else if (matchingSourceNodes.size() == 1) {
				MapActivity.this.startIsSet = true;
				MapActivity.this.preferenceDao
						.setRoutingStart(matchingSourceNodes.get(0).getId());
				MapActivity.this.routingSource = matchingSourceNodes.get(0);
			} else if (matchingSourceNodes.size() == 0) {
				Util.showSimpleDialog(
						getResources().getString(R.string.sourceNotFound),
						v.getContext());
			}
			if (MapActivity.this.startIsSet && MapActivity.this.endIsSet) {
				MapActivity.this.preferenceDao.setRoutingEnabled();
				setMapPositionAndRefresh(MapActivity.this.graph.getNodeById(
						MapActivity.this.routingSource.getId()).getPosition());
				hideRoutePanel();
			}
		}
	}
}
